home *** CD-ROM | disk | FTP | other *** search
/ ftp.mactech.com 2010 / ftp.mactech.com.tar / ftp.mactech.com / machack / Hacks95 / GregsHack.sit / Greg's Hack / Antialias.c next >
Text File  |  1995-06-24  |  5KB  |  205 lines

  1. /*
  2.      Greg's Hack — MacHack '95 Best Hack Contest (22-24 June 1995 )
  3.     Copyright © 1995 Gregory D. Landweber, ALL RIGHTS RESERVED
  4. */
  5.  
  6. #include <QDOffscreen.h>
  7. #include <A4Stuff.h>
  8. #include "AntiAlias.h"
  9.  
  10. void ShrinkMap ( PixMapHandle srceMap, PixMapHandle destMap, short width, short height);
  11.  
  12. GWorldPtr    smallWorld, largeWorld;
  13. long        table[16] = { 0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4 };
  14. long        table2[256];
  15. Rect        smallRect = { 0, 0, 32, 1024 },
  16.         largeRect = { 0, 0, 128, 4096 };
  17.  
  18. pascal void MyDrawChar ( char theChar )
  19. {
  20.     MyDrawText ( &theChar, 0, 1 );
  21. }
  22.  
  23. pascal void MyDrawString ( StringPtr theString )
  24. {
  25.     MyDrawText ( (Ptr)theString, 1, theString[0] );
  26. }
  27.  
  28. pascal void MyDrawText ( Ptr buffer, short offset, short len )
  29. {
  30.     GWorldPtr        saveGW;
  31.     GDHandle        saveGD;
  32.     short        txSize, txFont, txMode;
  33.     FontInfo        fInfo;
  34.     Rect            myRect, maskRect;
  35.     Point            penPt;
  36.     short        width;
  37.     short        pixelSize;
  38.     PixMapHandle    largePixMap;
  39.     Boolean        onScreen;
  40.     Boolean        colorPort;
  41.     Ptr            BaseAddr;
  42.  
  43.     EnterCodeResource();
  44.  
  45.     GetGWorld ( &saveGW, &saveGD );
  46.     pixelSize = (*(*saveGD)->gdPMap)->pixelSize;
  47.     
  48.     txFont = saveGW->txFont;
  49.     txSize = 4 * ( saveGW->txSize ? saveGW->txSize : ( LMGetSysFontSize() ? LMGetSysFontSize() : 12 ) );
  50.     txMode = saveGW->txMode;
  51.     
  52.     colorPort = ( (saveGW->portVersion & 0xC000) == 0xC000 );
  53.     BaseAddr = ((GrafPtr)saveGW)->portBits.baseAddr;
  54.     if ( colorPort )
  55.         BaseAddr = (*(PixMapHandle)BaseAddr)->baseAddr;
  56.         
  57.     onScreen = ( BaseAddr == LMGetScrnBase() );
  58.     
  59.     if (    !onScreen ||
  60.         ( saveGW->txSize >= 32 ) ||
  61.         ( txFont == 0 ) || 
  62.         ( txFont == 1/*&& txSize == 48*/ ) ||
  63.         ( txFont == 3 ) ||
  64.         ( ( ( pixelSize < 8 ) &&
  65.           ( ( pixelSize != 4 ) || TestDeviceAttribute ( saveGD, gdDevType ) ) ) ) ) {
  66.         
  67. #ifdef __powerc
  68.         CallUniversalProc ( oldDrawText, uppDrawTextProcInfo, buffer, offset, len );
  69. #else
  70.         ( ( DrawTextType ) oldDrawText ) ( buffer, offset, len );
  71. #endif
  72.  
  73.         ExitCodeResource();
  74.         return;
  75.     }
  76.     
  77.     if ( LMGetFractEnable() == 0 )
  78.         SetFractEnable ( true );
  79.     
  80.     GetFontInfo ( &fInfo );
  81.     
  82.     GetPen ( &penPt );
  83.  
  84.     SetGWorld ( largeWorld, 0 );
  85.     
  86.     TextFont ( txFont );
  87.     TextSize ( txSize );
  88.     
  89.     if ( LockPixels ( largePixMap = GetGWorldPixMap ( largeWorld ) ) ) {
  90.         Point        endPt;
  91.         
  92.         EraseRect ( &largeRect );
  93.         
  94.         TextFace ( saveGW->txFace );
  95.         
  96.         if ( txMode == grayishTextOr ) {
  97.             TextMode ( grayishTextOr );
  98.             txMode = srcOr;
  99.         }
  100.         else
  101.             TextMode ( srcCopy );
  102.         
  103.         MoveTo ( 0, largeRect.top + 4 * ( saveGW->txSize + 1 - fInfo.descent) );
  104.  
  105. #ifdef __powerc
  106.         CallUniversalProc ( oldDrawText, uppDrawTextProcInfo, buffer, offset, len );
  107. #else
  108.         ( ( DrawTextType ) oldDrawText ) ( buffer, offset, len );
  109. #endif
  110.         
  111.         GetPen ( &endPt );
  112.         width = ( endPt.h + 3 ) / 4;
  113.         
  114.         myRect.left    = penPt.h;
  115.         myRect.bottom    = penPt.v + fInfo.descent;
  116.         myRect.right    = myRect.left + width + 1;
  117.         myRect.top    = myRect.bottom - saveGW->txSize - 1;
  118.         
  119.         maskRect = myRect;
  120.         OffsetRect ( &maskRect, - maskRect.left, - maskRect.top );
  121.         {
  122.             PixMapHandle    smallPixMap, savePixMap;
  123.             
  124.             if ( !LockPixels ( smallPixMap = GetGWorldPixMap ( smallWorld ) ) )
  125.                 SysBeep ( 10 );
  126.             if ( !LockPixels ( savePixMap  = GetGWorldPixMap ( saveGW ) ) )
  127.                 SysBeep ( 10 );
  128.             
  129.             ShrinkMap ( largePixMap, smallPixMap, maskRect.right, maskRect.bottom );
  130.             SetGWorld ( saveGW, saveGD );
  131.             CopyBits ( (BitMap *)*smallPixMap, (BitMap *)*savePixMap,
  132.                        &maskRect, &myRect, txMode, 0L );
  133.             UnlockPixels ( smallPixMap );
  134.             UnlockPixels ( savePixMap);
  135.         }
  136.         UnlockPixels ( largePixMap );
  137.     }
  138.         
  139.     Move ( width, 0 );
  140.     
  141.     ExitCodeResource();    // hack
  142. }
  143.                     
  144. void ShrinkMap ( PixMapHandle srceMap, PixMapHandle destMap, short width, short height )
  145. {
  146.     Byte    *srceBase, *destBase, *destBase0,
  147.         *srceBase0, *srceBase1, *srceBase2, *srceBase3;
  148.     
  149.     short    row, byte;
  150.     short    rowBytes, numBytes;
  151.     long        *table3 = table2;
  152.     
  153.     if ( width >1024 )
  154.         width = 1024;
  155.     
  156.     if ( height > 32 )
  157.         height = 32;
  158.         
  159.     rowBytes = (*destMap)->rowBytes & 0x7FFF;
  160.     numBytes = ( ( width * 4 + 15 ) >> 4 ) << 1;
  161.     
  162.     srceBase = (Byte *)GetPixBaseAddr ( srceMap );
  163.     destBase = (Byte *)GetPixBaseAddr ( destMap );
  164.     destBase0 = destBase;
  165.     
  166.     if ( numBytes > rowBytes )
  167.         numBytes = rowBytes;
  168.  
  169.     for ( row = 0; row < height; row++ ) {
  170.         srceBase3 = rowBytes + ( srceBase2 = rowBytes + ( srceBase1 = rowBytes + ( srceBase0 = srceBase ) ) );
  171.         for ( byte = numBytes; byte > 0; byte-- ) {
  172.             long    result;
  173.             result = table3[*(srceBase0++)] + table3[*(srceBase1++)] + table3[*(srceBase2++)] +table3[*(srceBase3++)];
  174.             result -= ( result & 0x00001010 ) >> 4;
  175.             *(destBase0++) = result + (result >> 4);
  176.         }
  177.         srceBase += rowBytes << 2;
  178.         destBase0 = ( destBase += rowBytes );
  179.     }
  180. }
  181.  
  182. Boolean AntiAlias ( void )
  183. {
  184.     CTabHandle    ctab = GetCTable ( 4 + 32);
  185.     
  186.     {    long    i, j;
  187.         for ( i = 0; i < 16; i++ )
  188.             for ( j = 0; j < 16; j++ )
  189.                 table2[(i << 4 ) + j] = ( table[i] << 8 ) + table[j];
  190.     }
  191.  
  192.     if ( NewGWorld( &smallWorld, 4, &smallRect, ctab, 0, 0 ) != noErr ) {
  193.         DisposHandle( (Handle)ctab );
  194.         return false;
  195.     }
  196.     
  197.     if ( NewGWorld( &largeWorld, 1, &largeRect, 0, 0, 0 ) != noErr ) {
  198.         DisposeGWorld ( smallWorld );
  199.         return false;
  200.     }
  201.                     
  202.     SetFractEnable ( true );
  203.     
  204.     return true; 
  205. }